package org.hugoduncan.appam.server.impl;

import java.io.IOException;
import java.util.ArrayList;
import java.util.Collection;
import java.util.List;

import javax.servlet.ServletException;

import org.apache.abdera.model.Service;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.hugoduncan.appam.config.ComponentFactory;
import org.hugoduncan.appam.config.ServiceConfigurationProvider;
import org.hugoduncan.appam.model.ServiceComponent;
import org.hugoduncan.appam.server.AppServletRequest;
import org.hugoduncan.appam.server.AppServletResponse;
import org.hugoduncan.appam.server.Manager;
import org.hugoduncan.appam.server.PathHandler;

public class ManagerImpl implements Manager
{
    private static final Log log = LogFactory.getLog(ManagerImpl.class);
    
    private List<ServiceComponent> services=new ArrayList<ServiceComponent>();
    private ComponentFactory factory;
    private List<ServiceConfigurationProvider> serviceConfigurations;
    
    Collection<PathHandler> pathHandlers=new ArrayList<PathHandler>();
    

    public boolean process(AppServletRequest request,
                           AppServletResponse response)
        throws IOException, ServletException
    {
        if (services.size()==0)
            processConfiguration();
        
        for (ServiceComponent service:services)
            if (service.process(request, response))
                return true;
        for (PathHandler handler:pathHandlers)
            if (handler.process(request, response))
                return true;
        return false;
    }


    public void addService(ServiceComponent service) {
        services.add(service);
    }

    public void addPathHandler(PathHandler handler) {
        pathHandlers.add(handler);
    }
    
    @SuppressWarnings("unchecked")
    public void setConfiguration(List serviceConfigurations)
    {
        this.serviceConfigurations=serviceConfigurations;
    }

    private void processConfiguration() 
    {
        for (Object obj:serviceConfigurations)
        {
            try {
                ServiceConfigurationProvider provider=(ServiceConfigurationProvider) obj;
                Service service = provider.getService();
                if (service==null)
                {
                    log.error("Could not obtain service configuration");
                    return;
                }
                services.add(factory.construct(service));
            } catch (IOException e) {
                log.error("Could not construct service",e);
            }
        }
    }

    public void setFactory(ComponentFactory factory) {
        this.factory = factory;
    }

    public Collection<ServiceComponent> getServices() {
        return services;
    }
}
